<template>
  <div class="role-manage p-4" tabindex="0">
    <!-- 操作按钮区域 -->
    <div class="mb-4 flex flex-wrap gap-2 items-center">
      <el-input
        v-model="queryParams.roleName"
        placeholder="请输入角色名称"
        style="width: 200px"
        clearable
        @keyup.enter="handleSearch"
        @clear="handleSearch"
      >
        <template #prefix>
          <el-icon><Search /></el-icon>
        </template>
      </el-input>
      <el-button type="primary" @click="handleAdd" ref="addButton">
        <el-icon><Plus /></el-icon>
        新增
      </el-button>
      <el-button type="primary" plain @click="handleSearch">
        <el-icon><Search /></el-icon>
        查询
      </el-button>
      <el-button type="info" plain @click="handleReset">
        <el-icon><Refresh /></el-icon>
        重置
      </el-button>
      <el-button
        type="danger"
        plain
        @click="handleDelete"
        :disabled="!selectedRows.length"
      >
        <el-icon><Delete /></el-icon>
        删除
      </el-button>
    </div>

    <!-- 表格 -->
    <el-table
      v-loading="loading"
      :data="tableData"
      border
      @selection-change="handleSelectionChange"
    >
      <el-table-column type="selection" width="55" align="center" />
      <el-table-column label="#" type="index" width="60" align="center" />
      <el-table-column prop="roleName" label="角色名称" min-width="150" />
      <el-table-column prop="roleKey" label="角色标识" min-width="150" />
      <el-table-column
        prop="roleDescription"
        label="角色描述"
        min-width="200"
      />
      <el-table-column
        prop="roleStatus"
        label="角色状态"
        width="100"
        align="center"
      >
        <template #default="scope">
          <el-tag v-if="String(scope.row.status) === '0'" type="success"
            >正常</el-tag
          >
          <el-tag v-else type="danger">停用</el-tag>
        </template>
      </el-table-column>
      <el-table-column prop="createTime" label="创建时间" min-width="160" />
      <el-table-column label="操作" width="200" fixed="right">
        <template #default="scope">
          <div class="flex space-x-2">
            <el-button
              type="warning"
              size="small"
              plain
              @click="handleEdit(scope.row)"
            >
              修改
            </el-button>
            <el-button
              type="primary"
              size="small"
              plain
              @click="handleAuth(scope.row)"
            >
              授权
            </el-button>
            <el-button
              type="danger"
              size="small"
              plain
              @click="handleDeleteSingle(scope.row)"
            >
              删除
            </el-button>
          </div>
        </template>
      </el-table-column>
    </el-table>

    <!-- 分页 -->
    <div class="mt-4 flex items-center text-sm text-gray-500">
      <span>共 {{ total }} 条</span>
      <div class="ml-4 flex items-center">
        <el-select
          v-model="queryParams.pageSize"
          class="!w-[100px] mr-2"
          @change="handleSizeChange"
        >
          <el-option
            v-for="size in [10, 20, 30, 50]"
            :key="size"
            :label="`${size}条/页`"
            :value="size"
          />
        </el-select>
        <el-pagination
          v-model:current-page="queryParams.pageNum"
          :page-size="queryParams.pageSize"
          layout="prev, pager, next"
          :total="total"
          :pager-count="5"
          background
          @current-change="handleCurrentChange"
        />
        <span class="mx-2">前往</span>
        <el-input
          v-model="jumpPage"
          class="!w-[50px]"
          @keyup.enter="handleJumpPage"
        />
        <span class="mx-2">页</span>
      </div>
    </div>

    <!-- 角色添加/编辑抽屉 -->
    <el-drawer
      v-model="drawerVisible"
      :title="dialogTitle"
      :direction="direction"
      size="380px"
      :destroy-on-close="true"
      :close-on-click-modal="false"
    >
      <el-form
        ref="roleFormRef"
        :model="roleForm"
        :rules="roleFormRules"
        label-width="100px"
        @keyup.enter.native="submitForm"
      >
        <el-form-item label="角色名称" prop="roleName">
          <el-input
            v-model="roleForm.roleName"
            placeholder="请输入角色名称"
            @keyup.enter="submitForm"
          />
        </el-form-item>
        <el-form-item label="角色标识" prop="roleKey" v-if="!isEdit">
          <el-input
            v-model="roleForm.roleKey"
            placeholder="请输入角色标识"
            @keyup.enter="submitForm"
          />
        </el-form-item>
        <el-form-item label="角色等级">
          <el-input-number
            max="999"
            min="1"
            v-model="roleForm.roleLevel"
            placeholder="角色等级"
          ></el-input-number>
        </el-form-item>
        <el-form-item label="角色描述" prop="roleDescription">
          <el-input
            v-model="roleForm.roleDescription"
            placeholder="请输入角色描述"
            type="textarea"
            :rows="3"
          />
        </el-form-item>
      </el-form>
      <template #footer>
        <div class="dialog-footer">
          <el-button @click="drawerVisible = false">取消</el-button>
          <el-button type="primary" @click="submitForm" ref="submitButton"
            >确定</el-button
          >
        </div>
      </template>
    </el-drawer>

    <!-- 权限分配抽屉 -->
    <el-drawer
      v-model="authDrawerVisible"
      title="权限分配"
      direction="rtl"
      size="400px"
      :destroy-on-close="true"
      :close-on-click-modal="false"
    >
      <div class="p-4">
        <div class="mb-4">
          <span class="font-bold">角色名称：</span>
          <span>{{ currentRole.roleName }}</span>
        </div>
        <el-tree
          ref="permissionTreeRef"
          :data="permissionTree"
          :props="{ label: 'label', children: 'children' }"
          node-key="value"
          show-checkbox
          default-expand-all
          :default-checked-keys="checkedPermissions"
          :check-strictly="false"
          v-loading="permissionLoading"
        />
      </div>
      <template #footer>
        <div class="dialog-footer">
          <el-button @click="authDrawerVisible = false">取消</el-button>
          <el-button type="primary" @click="submitPermissions">确定</el-button>
        </div>
      </template>
    </el-drawer>
  </div>
</template>

<script setup>
import { ref, reactive, onMounted, watch } from 'vue'
import { ElMessage, ElMessageBox } from 'element-plus'
import {
  Search,
  Plus,
  Refresh,
  Delete,
  Download,
} from '@element-plus/icons-vue'
import {
  getrole,
  addrole,
  delrole,
  batchDelRole,
  updatarole,
  getRolePermissions,
  assignRolePermissions,
} from '@/api/role.js'

// 查询参数
const queryParams = reactive({
  roleName: '',
  pageNum: 1,
  pageSize: 10,
})

// 表格数据
const tableData = ref([])
const loading = ref(false)
const total = ref(0)
const jumpPage = ref(1)
const addButton = ref(null)
const selectedRows = ref([])

// 抽屉相关
const drawerVisible = ref(false)
const dialogTitle = ref('添加角色')
const direction = ref('rtl') // 从右向左打开
const isEdit = ref(false)
const roleFormRef = ref(null)
const roleForm = reactive({
  id: undefined,
  roleName: '',
  roleKey: '',
  roleDescription: '',
  roleLevel: 0,
})
const submitButton = ref(null)

// 权限分配相关
const authDrawerVisible = ref(false)
const permissionTreeRef = ref(null)
const permissionTree = ref([])
const checkedPermissions = ref([])
const permissionLoading = ref(false)
const currentRole = reactive({
  id: undefined,
  roleName: '',
})

// 表单验证规则
const roleFormRules = {
  roleName: [
    { required: true, message: '请输入角色名称', trigger: 'blur' },
    { min: 2, max: 50, message: '长度在 2 到 50 个字符', trigger: 'blur' },
  ],
  roleKey: [
    { required: true, message: '请输入角色标识', trigger: 'blur' },
    {
      pattern: /^[a-zA-Z0-9_]+$/,
      message: '角色标识只能包含字母、数字和下划线',
      trigger: 'blur',
    },
  ],
}

// 获取角色列表
const getRoleList = async () => {
  loading.value = true
  try {
    const { code, data, msg } = await getrole(queryParams)
    if (code === 500) {
      throw new Error(msg)
    }
    tableData.value = data.records || []
    total.value = data.total || 0
  } catch (error) {
    ElMessage.error(error.message || '获取角色列表失败')
  } finally {
    loading.value = false
  }
}

// 处理表格选择变化
const handleSelectionChange = (selection) => {
  selectedRows.value = selection
}

// 处理搜索
const handleSearch = () => {
  queryParams.pageNum = 1
  getRoleList()
}

// 处理重置
const handleReset = () => {
  queryParams.roleName = ''
  handleSearch()
}

// 处理分页大小变化
const handleSizeChange = (size) => {
  queryParams.pageSize = size
  getRoleList()
}

// 处理页码变化
const handleCurrentChange = (page) => {
  queryParams.pageNum = page
  getRoleList()
}

// 添加页面跳转功能
const handleJumpPage = () => {
  const pageNum = parseInt(jumpPage.value)
  if (
    isNaN(pageNum) ||
    pageNum < 1 ||
    pageNum > Math.ceil(total.value / queryParams.pageSize)
  ) {
    ElMessage.warning('请输入有效的页码')
    jumpPage.value = queryParams.pageNum
    return
  }
  queryParams.pageNum = pageNum
  getRoleList()
}

// 处理添加
const handleAdd = () => {
  resetForm()
  dialogTitle.value = '添加角色'
  isEdit.value = false
  drawerVisible.value = true
}

// 处理编辑
const handleEdit = (row) => {
  resetForm()
  dialogTitle.value = '修改角色'
  isEdit.value = true
  // 填充表单数据
  Object.keys(roleForm).forEach((key) => {
    roleForm[key] = row[key]
  })
  drawerVisible.value = true
}

// 处理批量删除
const handleDelete = () => {
  if (!selectedRows.value.length) {
    ElMessage.warning('请选择要删除的数据')
    return
  }

  const roleNames = selectedRows.value.map((item) => item.roleName).join('、')
  ElMessageBox.confirm(`确定要删除角色"${roleNames}"吗？`, '提示', {
    confirmButtonText: '确定',
    cancelButtonText: '取消',
    type: 'warning',
  })
    .then(async () => {
      try {
        const roleIds = selectedRows.value.map((item) => item.id)
        const { code, msg } = await batchDelRole(roleIds)
        if (code === 500) {
          ElMessage.error(msg)
          return
        }
        ElMessage.success('删除成功')
        getRoleList()
      } catch (error) {
        ElMessage.error(error.message || '删除失败')
      }
    })
    .catch(() => {})
}

// 处理单个删除
const handleDeleteSingle = (row) => {
  ElMessageBox.confirm(`确定要删除角色"${row.roleName}"吗？`, '提示', {
    confirmButtonText: '确定',
    cancelButtonText: '取消',
    type: 'warning',
  })
    .then(async () => {
      try {
        const { code, msg } = await delrole(row.id)
        if (code === 500) {
          ElMessage.error(msg)
          return
        }
        ElMessage.success('删除成功')
        getRoleList()
      } catch (error) {
        ElMessage.error(error.message || '删除失败')
      }
    })
    .catch(() => {})
}

// 处理授权
const handleAuth = async (row) => {
  currentRole.id = row.id
  currentRole.roleName = row.roleName

  // 清空之前选中的权限
  checkedPermissions.value = []
  permissionTree.value = []

  // 打开抽屉
  authDrawerVisible.value = true

  // 获取角色权限
  await loadRolePermissions(row.id)
}

// 加载角色权限
const loadRolePermissions = async (roleId) => {
  permissionLoading.value = true
  try {
    const { code, data, msg } = await getRolePermissions(roleId)
    if (code === 500) {
      throw new Error(msg)
    }
    // 设置权限树数据
    permissionTree.value = data.menuTreeVoList || []
    // 设置选中的权限ID
    checkedPermissions.value = data.checkedList || []
  } catch (error) {
    ElMessage.error(error.message || '获取角色权限失败')
  } finally {
    permissionLoading.value = false
  }
}

const handleCheckChange = (data, checked, indeterminate) => {
  console.log(data, checked, indeterminate)
}

// 保存角色权限
const submitPermissions = async () => {
  if (!permissionTreeRef.value) return

  // 获取选中的节点和半选中的节点
  const checkedNodes = permissionTreeRef.value.getCheckedNodes()
  const halfCheckedNodes = permissionTreeRef.value.getHalfCheckedNodes()

  // 收集所有选中节点和半选中节点的ID
  const menuIds = []

  // 处理选中的节点
  checkedNodes.forEach((node) => {
    // 添加节点自身的ID
    if (node.id) {
      menuIds.push(node.id)
    }

    // 添加节点的value (如果有且不为0)
    if (node.value && !menuIds.includes(node.value)) {
      menuIds.push(node.value)
    }

    // 递归查找并添加所有父节点ID
    if (node.parentId && !menuIds.includes(node.parentId)) {
      menuIds.push(node.parentId)

      // 查找祖先节点
      let currentNode = permissionTree.value.find(
        (item) => item.id === node.parentId || item.value === node.parentId
      )
      while (currentNode && currentNode.parentId) {
        if (!menuIds.includes(currentNode.parentId)) {
          menuIds.push(currentNode.parentId)
        }
        currentNode = permissionTree.value.find(
          (item) =>
            item.id === currentNode.parentId ||
            item.value === currentNode.parentId
        )
      }
    }
  })

  // 处理半选中的节点
  halfCheckedNodes.forEach((node) => {
    if (node.id && !menuIds.includes(node.id)) {
      menuIds.push(node.id)
    }
    if (node.value && !menuIds.includes(node.value)) {
      menuIds.push(node.value)
    }
  })

  console.log('选中的节点ID集合：', menuIds)

  try {
    const { code, msg } = await assignRolePermissions({
      roleId: currentRole.id,
      menuIds: menuIds,
    })

    if (code === 500) {
      ElMessage.error(msg)
      return
    }

    ElMessage.success('权限分配成功')
    authDrawerVisible.value = false
  } catch (error) {
    ElMessage.error(error.message || '权限分配失败')
  }
}

// 处理导入
const handleImport = () => {
  ElMessage.info('导入功能待实现')
}

// 重置表单
const resetForm = () => {
  roleForm.id = undefined
  roleForm.roleName = ''
  roleForm.roleKey = ''
  roleForm.roleDescription = ''
  roleForm.roleLevel = 1
  // 延迟重置校验结果
  setTimeout(() => {
    roleFormRef.value?.resetFields()
  }, 0)
}

// 处理提交表单
const submitForm = async () => {
  if (!roleFormRef.value) return

  await roleFormRef.value.validate(async (valid) => {
    if (valid) {
      try {
        if (isEdit.value) {
          // 调用更新角色接口
          const { code, msg } = await updatarole(roleForm)
          if (code === 500) {
            ElMessage.error(msg)
            return
          } else {
            ElMessage.success('修改成功')
          }
        } else {
          // 调用添加角色接口
          const { code, msg } = await addrole(roleForm)
          if (code === 500) {
            ElMessage.error(msg)
            return
          } else {
            ElMessage.success('添加成功')
          }
        }
        drawerVisible.value = false
        getRoleList()
      } catch (error) {
        ElMessage.error(error.message || '操作失败')
      }
    }
  })
}

// 监听pageNum变化，同步更新jumpPage
watch(
  () => queryParams.pageNum,
  (newVal) => {
    jumpPage.value = newVal
  }
)

onMounted(() => {
  getRoleList()
})
</script>

<style lang="less" scoped>
.role-manage {
  background-color: #fff;
  border-radius: 4px;
  box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
}
.role-manage {
  background-color: #fff;
  border-radius: 4px;
  box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
  .el-table {
    height: calc(100vh - 270px);
  }
}
</style>
